/*
 * Copyright (C) 2008,2009,2010,2011  Paulo Cesar Pereira de Andrade.
 *
 * This is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This software is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * Authors:
 *	Paulo Cesar Pereira de Andrade
 */

#ifndef _eparser_h
#define _eparser_h

#include "etypes.h"

#define eattr_const		(1 << 0)
#define eattr_extern		(1 << 1)
#define eattr_static		(1 << 2)

/*
 * Types
 */
enum etoken {
    /* special tokens */
    tok_eof		= -1,

    /*----------------	kind == tok_type	----------------*/
    /* primary tokens */
    tok_type,
    tok_symbol,
    tok_number,
    tok_string,

    /* macro tokens */
    tok_FILE,
    tok_LINE,
    tok_FUNCTION,
    tok_VA_ARGS,
    tok_DATE,
    tok_TIME,
    tok_COUNTER,
    tok_stringify,
    tok_concat,

    /*----------------	kind == tok_list	----------------*/
    /* punctuation */
    tok_list,
    tok_elist,
    tok_vector,
    tok_evector,
    tok_brace,
    tok_ebrace,

    tok_progn,
    tok_collon,
    tok_comma,
    tok_field,

    tok_ellipsis,

    /*----------------	kind == tok_set		----------------*/
    /* assignment */
    tok_set,
    tok_andset,
    tok_orset,
    tok_xorset,
    tok_mul2set,
    tok_div2set,
    tok_shlset,
    tok_shrset,
    tok_addset,
    tok_subset,
    tok_mulset,
    tok_divset,
    tok_trunc2set,
    tok_remset,

    /*----------------	kind == tok_logop	----------------*/
    /* logic operators */
#define tok_logop	tok_andand
    tok_andand,
    tok_oror,

    /*----------------	kind == tok_logcmp	----------------*/
    /* number comparison */
#define tok_logcmp	tok_ne
    tok_ne,
    tok_lt,
    tok_le,
    tok_eq,
    tok_ge,
    tok_gt,

    /*----------------	kind == tok_bitop	----------------*/
    /* bit operations */
#define tok_bitop	tok_and
    tok_and,
    tok_or,
    tok_xor,

    /*----------------	kind == tok_shift	----------------*/
    /* arithmetic shift */
#define tok_shift	tok_mul2
    tok_mul2,
    tok_div2,
    tok_shl,
    tok_shr,

    /*----------------	kind == tok_addsub	----------------*/
    /* addition and subtraction */
#define tok_addsub	tok_add
    tok_add,
    tok_sub,

    /*----------------	kind == tok_muldivrem	----------------*/
    /* multiplication, division and modulo */
#define tok_muldivrem	tok_mul
    tok_mul,
    tok_div,
    tok_trunc2,
    tok_rem,

    /* function like binary operators */
    tok_atan2,
    tok_pow,
    tok_hypot,
    tok_complex,
    tok_subtypeof,
    tok_renew,

    /*----------------	kind == tok_unary	----------------*/
    /* left side unary operations */
#define tok_unary	tok_sizeof
    tok_sizeof,
    tok_typeof,
    tok_new,
    tok_address,
    tok_pointer,
    tok_rankof,

    tok_not,
    tok_com,
    tok_plus,
    tok_neg,

    /* function like unary operators */
    tok_signbit,
    tok_signum,
    tok_rational,
    tok_integer_p,
    tok_rational_p,
    tok_float_p,
    tok_real_p,
    tok_complex_p,
    tok_number_p,
    tok_finite_p,
    tok_inf_p,
    tok_nan_p,
    tok_num,
    tok_den,
    tok_real,
    tok_imag,
    tok_arg,
    tok_conj,
    tok_floor,
    tok_trunc,
    tok_round,
    tok_ceil,
    tok_abs,
    tok_sqrt,
    tok_cbrt,
    tok_sin,
    tok_cos,
    tok_tan,
    tok_asin,
    tok_acos,
    tok_atan,
    tok_sinh,
    tok_cosh,
    tok_tanh,
    tok_asinh,
    tok_acosh,
    tok_atanh,
    tok_proj,
    tok_exp,
    tok_log,
    tok_log2,
    tok_log10,

    /*----------------	kind == tok_incdec	----------------*/
    /* right side unary operations */
#define tok_incdec	tok_inc
    tok_inc,
    tok_dec,
    tok_postinc,
    tok_postdec,
    /* [ and ( are treated specially */

    /*----------------	kind == tok_ternary	----------------*/
    /* ternary operator */
    tok_ternary,

    /* this . field */
    tok_this,

    /*----------------	kind == tok_if		----------------*/
    /* keywords */
    tok_if,
    tok_else,
    tok_goto,
    tok_return,

    tok_switch,
    tok_case,
    tok_default,
    tok_break,
    tok_continue,

    tok_try,
    tok_catch,
    tok_throw,
    tok_always,

    /*----------------	kind == tok_loop	----------------*/
    /* looping tokens */
#define tok_loop	tok_for
    tok_for,
    tok_do,
    tok_while,

    /*----------------	kind == tok_attribute	----------------*/
#define tok_attribute	tok_struct
    /* order is tok_struct, tok_class, tok_union */
    tok_struct,
    tok_class,
    tok_union,

    tok_typedef,

    /*----------------	kind == tok_composed	----------------*/
    /* composed tokens */
#define tok_composed	tok_label
    tok_label,
    tok_code,		/* '{' in code context */
    tok_data,		/* '{' in data context */
    tok_new_type_data,
    tok_function,
    tok_declaration,
    tok_expression,
    tok_statement,
    tok_offset,
    tok_explicit,	/* explicit class method call */
    tok_ctor,
};

/*
 * Prototypes
 */
extern eobject_t
eparse(void);

extern etoken_t
ekind_of(etoken_t);

extern void
init_parser(void);

/*
 * Externs
 */
extern esymbol_t *symbol_new, *symbol_this, *symbol_throw;
extern ehash_t *hash_annotation;

#endif /* _eparser_h */
